

public class SocWear {

	/****************************************
	 * Attributes
	 ****************************************/
	public iCATch316 iCatch;
	public GUI gui;
	public TwitterManager tm;
	public MessengerManager mm;
	public PreferenceManager pm;
	public DeviceManager dm;
	public LocationManager lm;
	
	public boolean isTyping;
	
	private Thread twitterWorker;
	private Thread inputDeviceListener;	
	private Thread finder;
	
	/****************************************
	 * Constructor
	 ****************************************/
	public SocWear(GUI gui, String preferenceFile) {

		iCatch = new iCATch316();

		this.gui = gui;
		this.gui.setLocationRelativeTo(null);
		this.gui.setVisible(true);
		setGUIListeners();
		
		tm = new TwitterManager();
		mm = new MessengerManager();
		pm = new PreferenceManager(preferenceFile);
		lm = new LocationManager("D:/AppServ/www/test.txt");
		
		// Connect to Twitter
		tm.connectToTwitter();
		
		isTyping = false;
	}
	
	
	// Methods	
	/****************************************
	 * Connect to iCATch
	 ****************************************/
	public void connectToiCATch(String COMPort) {
		iCatch.connect(COMPort);
		dm = new DeviceManager(iCatch);
		
		listenToLatestTweet();
		listenToInputDevices();
		findFriendsNearBy();
	}
	
	
	/****************************************
	 * Sleep
	 ****************************************/
	public static void sleep(long millisecond) {
		try {
			Thread.sleep(millisecond);
		} catch (InterruptedException e) {
			e.printStackTrace();
		}
	}
	
	
	/****************************************
	 * Keep checking if there is latest tweet
	 ****************************************/
	private void listenToLatestTweet() {

		// Use a new thread to listen to latest tweets
		twitterWorker = new Thread(new Runnable() {
			public void run() {
				String lastTweet = "";
				String currentTweet;
				String state;
				int interval = 2000;

				// Keep it running
				while (true) {
					currentTweet = tm.getLatestTweet();
					state = "";
					
					 // New tweet
					if (!currentTweet.equals(lastTweet)) {
						// Happy tweet
						if (tm.tweetIsHappy(currentTweet)) {
							((Buzzer)dm.getDeviceByType(Device.BUZZER)).playSound('B');
							state = "(Happy)";
						}
						// Sad tweet
						else if (tm.tweetIsSad(currentTweet)) {
							((VibrationMotor)dm.getDeviceByType(Device.VIBRATION_MOTOR)).vibrate();
							state = "(Sad)";
						}
						// Danger tweet
						else if (tm.tweetIsDanger(currentTweet)) {
							((Buzzer)dm.getDeviceByType(Device.BUZZER)).playSound('D');
							state = "(Danger)";
						}
						// Normal tweet
						else {
							((Buzzer)dm.getDeviceByType(Device.BUZZER)).playSound('E');
						}

						gui.textArea.append("\n" + "New tweet! " + currentTweet + state);
					}

					lastTweet = currentTweet;

					sleep(interval);
				}
			}
		});

		// Start the thread
		twitterWorker.start();
	}

	
	/****************************************
	 * Wait for input devices' signal
	 ****************************************/
	private void listenToInputDevices() {

		// Use a new thread to listen to input devices readings
		inputDeviceListener = new Thread(new Runnable() {
			public void run() {
				
				// Keep it running
				while (true) {
					
					// Get a joystick
					Joystick joystick = (Joystick) dm.getDeviceByType(Device.JOYSTICK);
					Buzzer buzzer = (Buzzer) dm.getDeviceByType(Device.BUZZER);
					String[] msg = pm.getAllDefaultMessages();
					int direction = joystick.getDirection();
					
					switch(direction) {
					case Joystick.UP:
						tm.tweet(msg[0]);
						System.out.println(msg[0]); // Debug
						buzzer.playSound('A');
						break;
					
					case Joystick.RIGHT:
						tm.tweet(msg[1]);
						System.out.println(msg[1]); // Debug
						buzzer.playSound('A');
						break;
					
					case Joystick.DOWN:
						tm.tweet(msg[2]);
						System.out.println(msg[2]); // Debug
						buzzer.playSound('A');
						break;
						
					case Joystick.LEFT:
						tm.tweet(msg[3]);
						System.out.println(msg[3]); // Debug
						buzzer.playSound('A');
						break;	
						
					case Joystick.PRESSED:
						Location location = lm.getMyLocation();
						
						lm.shareMyLocation();
						
						String tempMsg = "I am in " + location.name;
						tm.tweet(tempMsg);
						
						buzzer.playSound('B');
						break;
					}
					
					// Set update interval
					sleep(300);
				}
			}
		});

		// Start the thread
		inputDeviceListener.start();
	}
	
	
	/****************************************
	 * Find friends nearby
	 ****************************************/
	private void findFriendsNearBy() {
		// Keep tracking whether there are friends nearby
		finder = new Thread(new Runnable() {
			public void run() {
				int interval = 5000;

				// Keep it running
				while (true) {
					if (lm.friendNearBy()) {
						((VibrationMotor)dm.getDeviceByType(Device.VIBRATION_MOTOR)).vibrate();
						sleep(200);
						((Buzzer) dm.getDeviceByType(Device.BUZZER)).playSound('C');
						gui.textArea.append("\nA friend is nearby!");
					}

					sleep(interval);
				}
			}
		});

		// Start the thread
		finder.start();
	}
	
	/****************************************
	 * Set GUI listeners
	 ****************************************/
	private void setGUIListeners() {

	}
}
